#include "stdafx.h"
#include "rot.h"
#include "msg.h"


CComRunningObjectTableImpl::CComRunningObjectTableImpl()
{

}

CComRunningObjectTableImpl::~CComRunningObjectTableImpl()
{
	logi("CComRunningObjectTableImpl::~CComRunningObjectTableImpl");
}

std_method_impl CComRunningObjectTableImpl::CreateInstance(IBase* rot, REFCLSID clsid, IBase* punk, REFIID iid, void **ppv)
{

	SYNC_OBJ(&m_lockSection)
	HRESULT hr = S_OK;
	hr = IsRunning(CLSID_CObjectLoader);
	rc_assert(hr == S_OK, E_FAIL);
	
	RUNNINGTABLEITEM& Item = m_map[CLSID_CObjectLoader];

	CompoentLoaderPtr pICompoentLoader;
	pICompoentLoader.dispose();

	hr = Item.m_ptr->QueryInterface(IID_ICompoentLoader, (void**)&pICompoentLoader);
	rc_assert(hr == S_OK, E_FAIL);

	hr = pICompoentLoader->CreateInstance(rot, clsid, punk, iid, ppv);
	rc_assert(hr == S_OK, E_FAIL);

	return S_OK;
}
std_method_impl CComRunningObjectTableImpl::Register(REFCLSID clsid, LPCSTR progId, IBase *punk, UINT id)
{
	SYNC_OBJ(&m_lockSection)
	rc_assert(S_OK != IsRunning(clsid), E_FAIL);
	RUNNINGTABLEITEM& Item = m_map[clsid];
	Item.progid = progId;
	Item.cls = clsid;
	Item.index = id;
	return punk->QueryInterface(IID_IBase, (void**)&Item.m_ptr);
}

std_method_impl CComRunningObjectTableImpl::Revoke(REFCLSID clsid)
{
	SYNC_OBJ(&m_lockSection)
	rc_assert(S_OK == IsRunning(clsid), E_INVALIDARG);
	m_map.erase(clsid);
	return S_OK;
}

std_method_impl CComRunningObjectTableImpl::IsRunning(REFCLSID clsid)
{
	return m_map.end() != m_map.find(clsid) ? S_OK : S_FALSE;
}

std_method_impl CComRunningObjectTableImpl::GetObject(REFCLSID clsid, REFIID iid, IBase **ppunk)
{
	SYNC_OBJ(&m_lockSection)
	return GetBaseObject(clsid, iid, ppunk);
}

std_method_impl CComRunningObjectTableImpl::RevokeAll()
{
	SYNC_OBJ(&m_lockSection)
	m_map.clear();
	return S_OK;
}

std_method_type_impl(LPCSTR) CComRunningObjectTableImpl::ProgIDFromCLSID(REFCLSID clsid)
{
	SYNC_OBJ(&m_lockSection)
	OBJMAP::iterator it = m_map.find(clsid);
	rs_assert((it != m_map.end()), it->second.progid.c_str())
	CompoentLoaderPtr pICompoentLoader;
	rc_assert(S_SUCCEEDED(GetBaseObject(CLSID_CObjectLoader, IID_ICompoentLoader, (IBase**)&pICompoentLoader)), "");
	rc_assert(pICompoentLoader, "");
	return pICompoentLoader->ProgIDFromCLSID(clsid);
}

std_method_type_impl(CLSID) CComRunningObjectTableImpl::CLSIDFromProgID(LPCSTR lpProgId)
{
	SYNC_OBJ(&m_lockSection)
	CompoentLoaderPtr pICompoentLoader;
	rc_assert(S_SUCCEEDED(GetBaseObject(CLSID_CObjectLoader, IID_ICompoentLoader, (IBase**)&pICompoentLoader)), COMPONENT_NULL);
	rc_assert(pICompoentLoader, COMPONENT_NULL);
	return pICompoentLoader->CLSIDFromProgID(lpProgId);
}

std_method_type_impl(ULONG) CComRunningObjectTableImpl::GetObjectCount()
{
	SYNC_OBJ(&m_lockSection)
	return m_map.size();
}
std_method_impl CComRunningObjectTableImpl::CreateMessage(IBase** pMsg)
{
	CMsgImpl* pObject = ALLOC_NEW CMsgImpl();
	rc_assert(pObject != NULL, E_FAIL)
	return pObject->QueryInterface(IID_IMsg, (void**)pMsg);
}
std_method_impl CComRunningObjectTableImpl::SendMessage(REFCLSID sn, REFCLSID tn, ULONG gp, UINT msg, IBase* pMsg)
{
	return S_OK;
}
std_method_impl CComRunningObjectTableImpl::PostMessage(REFCLSID sn, REFCLSID tn, ULONG gp, UINT msg, IBase* pMsg)
{
	return S_OK;
}

std_method_impl CComRunningObjectTableImpl::GetBaseObject(REFCLSID clsid, REFIID iid, IBase **ppunk)
{
	OBJMAP::iterator it = m_map.find(clsid);
	rc_assert((m_map.end() != it), E_INVALIDARG);
	rc_assert(it->second.m_ptr, E_INVALIDARG);
	return it->second.m_ptr->QueryInterface(iid, (void**)ppunk);
}
